7  UK Postcode Maps

Author

Chrissy h Roberts

7.1 Background

This is a basic tutorial on how to load shapefiles and geopoints to a leaflet map.

There is a lot more detailed information here [https://rstudio.github.io/leaflet/](https://rstudio.github.io/leaflet/)

The example is hopefully useful as it uses UK postcode and district shapefiles, which are commonly useful for a variety of purposes.

UK Postcode data can be found here

https://www.freemaptools.com/map-tools.htm

UK district shapefiles are available here

https://www.ordnancesurvey.co.uk/opendatadownload/products.html

7.2 Libraries

library(tidyverse)
── Attaching core tidyverse packages ──────────────────────── tidyverse 2.0.0 ──
✔ dplyr     1.1.3     ✔ readr     2.1.4
✔ forcats   1.0.0     ✔ stringr   1.5.0
✔ ggplot2   3.4.4     ✔ tibble    3.2.1
✔ lubridate 1.9.3     ✔ tidyr     1.3.0
✔ purrr     1.0.2     
── Conflicts ────────────────────────────────────────── tidyverse_conflicts() ──
✖ dplyr::filter() masks stats::filter()
✖ dplyr::lag()    masks stats::lag()
ℹ Use the conflicted package (<http://conflicted.r-lib.org/>) to force all conflicts to become errors
library(sf)
Linking to GEOS 3.11.0, GDAL 3.5.3, PROJ 9.1.0; sf_use_s2() is TRUE
library(knitr)
library(leaflet)

7.3 Data

7.3.1 Create a folder to house data

if(!dir.exists("data/ukpostcodes"))(dir.create("data/ukpostcodes"))
[1] TRUE
system("rm -rf data/ukpostcodes/*")

7.4 Download a list of UK postcodes and gps locations

download.file(url = "https://data.freemaptools.com/download/full-uk-postcodes/ukpostcodes.zip",destfile =paste("data/ukpostcodes/ukpostcodes.zip"))

system ("unzip data/ukpostcodes/ukpostcodes.zip -d data/ukpostcodes/")

7.5 Download a list of UK district shapefiles

# set a timeout proportional to the size of the dataset and the speed of the connection
options(timeout=300)

download.file(url = "https://api.os.uk/downloads/v1/products/BoundaryLine/downloads?area=GB&format=ESRI%C2%AE+Shapefile&redirect",destfile =paste("data/ukpostcodes/bdline_essh_gb.zip"))

system ("unzip data/ukpostcodes/bdline_essh_gb.zip -d data/ukpostcodes/")

7.6 Read Postcode data

ukpostcodes <- read_csv("data/ukpostcodes/ukpostcodes.csv")
Rows: 1794534 Columns: 4
── Column specification ────────────────────────────────────────────────────────
Delimiter: ","
chr (1): postcode
dbl (3): id, latitude, longitude

ℹ Use `spec()` to retrieve the full column specification for this data.
ℹ Specify the column types or set `show_col_types = FALSE` to quiet this message.

7.7 Make a small sample of all postcodes

sample<-ukpostcodes[sample(1:nrow(ukpostcodes),size = 100),] %>% 
  mutate(
    latitude = as.numeric(latitude),
    longitude = as.numeric(longitude)
  )
head(sample)
# A tibble: 6 × 4
       id postcode latitude longitude
    <dbl> <chr>       <dbl>     <dbl>
1  441517 S42 5AZ      53.2    -1.40 
2  937107 LA12 0AE     54.2    -3.09 
3  187212 TN26 2PB     51.1     0.894
4  828394 M33 3HH      53.4    -2.30 
5 2582046 WA5 8AA      53.4    -2.64 
6  785461 MK7 8DQ      52.0    -0.683

7.8 Read in shapefiles to a map

map = read_sf("data/ukpostcodes/Data/GB/county_region.dbf")
mapproj <- st_transform(map, st_crs("+proj=longlat +init=epsg:4326 +ellps=WGS84 +datum=WGS84 +no_defs"))
Warning in CPL_crs_from_input(x): GDAL Message 1: +init=epsg:XXXX syntax is
deprecated. It might return a CRS with a non-EPSG compliant axis order.
leaflet(mapproj) %>% 
    addTiles() %>% 
  addMeasure(primaryLengthUnit="kilometers", secondaryLengthUnit="meters")  %>%
  addScaleBar(options = c(imperial = FALSE)) %>%  
  addPolygons(color = "green",label = mapproj$NAME) %>% 
  addCircleMarkers(lng = sample$longitude,lat = sample$latitude,label = sample$postcode,radius = 0.3)

7.8.1 remove data

system("rm -rf data/ukpostcodes/")